package com.example.blogapi.controller;

import com.example.blogapi.model.Tag;
import com.example.blogapi.service.TagService;
import com.example.blogapi.util.HttpUtil;
import com.example.blogapi.util.JsonUtil;
import com.sun.net.httpserver.HttpExchange;
import com.sun.net.httpserver.HttpHandler;

import java.io.IOException;
import java.sql.SQLException;
import java.util.List;
import java.util.Map;

public class TagController implements HttpHandler {
    private final TagService tagService;

    public TagController() {
        this.tagService = new TagService();
    }

    @Override
    public void handle(HttpExchange exchange) throws IOException {
        String method = exchange.getRequestMethod();
        String path = exchange.getRequestURI().getPath();

        try {
            if (method.equals("OPTIONS")) {
                handleOptionsRequest(exchange);
            } else if (method.equals("GET") && path.matches("/api/tags/?")) {
                handleGetAllTags(exchange);
            } else if (method.equals("GET") && path.matches("/api/tags/\\d+/?")) {
                handleGetTagById(exchange);
            } else if (method.equals("POST") && path.matches("/api/tags/?")) {
                handleCreateTag(exchange);
            } else if (method.equals("PUT") && path.matches("/api/tags/\\d+/?")) {
                handleUpdateTag(exchange);
            } else if (method.equals("DELETE") && path.matches("/api/tags/\\d+/?")) {
                handleDeleteTag(exchange);
            } else {
                String response = JsonUtil.toJson(Map.of("error", "Not found"));
                HttpUtil.sendResponse(exchange, 404, response);
            }
        } catch (Exception e) {
            e.printStackTrace();
            String response = JsonUtil.toJson(Map.of("error", e.getMessage()));
            HttpUtil.sendResponse(exchange, 500, response);
        }
    }

    private void handleOptionsRequest(HttpExchange exchange) throws IOException {
        HttpUtil.sendResponse(exchange, 200, "");
    }

    private void handleGetAllTags(HttpExchange exchange) throws IOException, SQLException {
        List<Tag> tags = tagService.getAllTags();
        String response = JsonUtil.toJson(tags);
        HttpUtil.sendResponse(exchange, 200, response);
    }

    private void handleGetTagById(HttpExchange exchange) throws IOException, SQLException {
        Long id = HttpUtil.extractIdFromPath(exchange.getRequestURI().getPath(), "/api/tags/(\\d+)/?");
        
        Tag tag = tagService.getTagById(id);
        if (tag != null) {
            String response = JsonUtil.toJson(tag);
            HttpUtil.sendResponse(exchange, 200, response);
        } else {
            String response = JsonUtil.toJson(Map.of("error", "Tag not found"));
            HttpUtil.sendResponse(exchange, 404, response);
        }
    }

    private void handleCreateTag(HttpExchange exchange) throws IOException, SQLException {
        String requestBody = HttpUtil.getRequestBody(exchange);
        Tag tag = JsonUtil.fromJson(requestBody, Tag.class);
        
        try {
            Tag createdTag = tagService.createTag(tag);
            String response = JsonUtil.toJson(createdTag);
            HttpUtil.sendResponse(exchange, 201, response);
        } catch (IllegalArgumentException e) {
            String response = JsonUtil.toJson(Map.of("error", e.getMessage()));
            HttpUtil.sendResponse(exchange, 400, response);
        }
    }

    private void handleUpdateTag(HttpExchange exchange) throws IOException, SQLException {
        Long id = HttpUtil.extractIdFromPath(exchange.getRequestURI().getPath(), "/api/tags/(\\d+)/?");
        String requestBody = HttpUtil.getRequestBody(exchange);
        Tag tag = JsonUtil.fromJson(requestBody, Tag.class);
        
        try {
            Tag updatedTag = tagService.updateTag(id, tag);
            String response = JsonUtil.toJson(updatedTag);
            HttpUtil.sendResponse(exchange, 200, response);
        } catch (IllegalArgumentException e) {
            String response = JsonUtil.toJson(Map.of("error", e.getMessage()));
            HttpUtil.sendResponse(exchange, 400, response);
        }
    }

    private void handleDeleteTag(HttpExchange exchange) throws IOException, SQLException {
        Long id = HttpUtil.extractIdFromPath(exchange.getRequestURI().getPath(), "/api/tags/(\\d+)/?");
        
        try {
            boolean deleted = tagService.deleteTag(id);
            if (deleted) {
                HttpUtil.sendResponse(exchange, 204, "");
            } else {
                String response = JsonUtil.toJson(Map.of("error", "Failed to delete tag"));
                HttpUtil.sendResponse(exchange, 500, response);
            }
        } catch (IllegalArgumentException e) {
            String response = JsonUtil.toJson(Map.of("error", e.getMessage()));
            HttpUtil.sendResponse(exchange, 400, response);
        }
    }
}